using System;
using System.Collections.Generic;
using System.Text;
using System.Xml;

namespace MapCop
{
    public class Map
    {
        private XmlDocument _mapDocument;

        private string pagesXPath = @"/mapsource/Pages/Page";
        private string precedenceXPath = @"/mapsource/ScriptTypePrecedence";

        public Map(string fileName)
        {
            if (!System.IO.File.Exists(fileName))
                throw new System.IO.FileNotFoundException(String.Format("Unable to locate map file {0}.", fileName), fileName);

            _mapDocument = new XmlDocument();
            using (System.IO.StreamReader reader = new System.IO.StreamReader(fileName, Encoding.UTF8))
                _mapDocument.Load(reader);

            System.Xml.XmlElement docElement = _mapDocument.DocumentElement;

            _mapperVersion = docElement.Attributes["BizTalkServerMapperTool_Version"].Value;
            _version = docElement.Attributes["Version"].Value;
            _xRange = Convert.ToInt32(docElement.Attributes["XRange"].Value);
            _yRange = Convert.ToInt32(docElement.Attributes["YRange"].Value);

            _omitXmlDeclaration = CastToBool(docElement.Attributes["OmitXmlDeclaration"]);
            _treatElementsAsRecords = CastToBool(docElement.Attributes["TreatElementsAsRecords"]);
            _optimizeValueMapping = CastToBool(docElement.Attributes["OptimizeValueMapping"]);
            _generateDefaultFixedNodes = CastToBool(docElement.Attributes["GenerateDefaultFixedNodes"]);
            _copyPIs = CastToBool(docElement.Attributes["CopyPIs"]);
            _ignoreNamespacesForLinks = CastToBool(docElement.Attributes["IgnoreNamespacesForLinks"]);

            _xmlVersion = docElement.Attributes["xmlVersion"].Value;
            _method = docElement.Attributes["method"].Value;

            XmlNodeList pageNodeList = _mapDocument.SelectNodes(pagesXPath);
            foreach (XmlNode loopPage in pageNodeList)
                _pages.Add(new MapPage(this, loopPage));

            XmlNode precedenceNode = _mapDocument.SelectSingleNode(precedenceXPath);
            foreach (XmlNode loopScript in precedenceNode.ChildNodes)
                _scriptTypePrecedences.Add(new ScriptTypePrecedence(this, loopScript.Name, loopScript.Attributes["Enabled"].Value));
        }

        private bool CastToBool(System.Xml.XmlAttribute attrib)
        {
            if (attrib == null) return false;
            if (attrib.Value.ToLower() == "yes")
                return true;
            else
                return false;
        }

        private List<ScriptTypePrecedence> _scriptTypePrecedences = new List<ScriptTypePrecedence>();
        public List<ScriptTypePrecedence> ScriptTypePrecedences
        {
            get
            {
                return _scriptTypePrecedences;
            }
        }

        private List<MapPage> _pages = new List<MapPage>();
        public List<MapPage> Pages
        {
            get
            {
                return _pages;
            }
        }

        private string _mapperVersion;
        public string MapperVersion
        {
            get
            {
                return _mapperVersion;
            }
        }

        private string _version;
        public string Version
        {
            get
            {
                return _version;
            }
        }

        private int _xRange;
        public int XRange
        {
            get
            {
                return _xRange;
            }
        }

        private int _yRange;
        public int YRange
        {
            get
            {
                return _yRange;
            }
        }

        private bool _omitXmlDeclaration;
        public bool OmitXmlDeclaration
        {
            get
            {
                return _omitXmlDeclaration;
            }
        }

        private bool _treatElementsAsRecords;
        public bool TreatElementsAsRecords
        {
            get
            {
                return _treatElementsAsRecords;
            }
        }

        private bool _optimizeValueMapping;
        public bool OptimizeValueMapping
        {
            get
            {
                return _optimizeValueMapping;
            }
        }

        private bool _generateDefaultFixedNodes;
        public bool GenerateDefaultFixedNodes
        {
            get
            {
                return _generateDefaultFixedNodes;
            }
        }

        private bool _copyPIs;
        public bool CopyPIs
        {
            get
            {
                return _copyPIs;
            }
        }

        private bool _ignoreNamespacesForLinks;
        public bool IgnoreNamespacesForLinks
        {
            get
            {
                return _ignoreNamespacesForLinks;
            }
        }

        private string _method;
        public string Method
        {
            get
            {
                return _method;
            }
        }

        private string _xmlVersion;
        public string XmlVersion
        {
            get
            {
                return _xmlVersion;
            }
        }
    }
}
